home *** CD-ROM | disk | FTP | other *** search
-
- elf_begin(3E) Silicon Graphics elf_begin(3E)
-
- NAME
- elf_begin - make a file descriptor
-
- SYNOPSIS
- cc [flag ...] file ... -lelf [library ...]
-
- #include <libelf.h>
-
- Elf *elf_begin(int fildes, Elf_Cmd cmd, Elf *ref);
-
- DESCRIPTION
- elf_begin, elf_next, elf_rand, and elf_end work together to process ELF
- object files, either individually or as members of archives. After
- obtaining an ELF descriptor from elf_begin, the program may read an
- existing file, update an existing file, or create a new file. fildes is
- an open file descriptor that elf_begin uses for reading or writing. The
- initial file offset [see lseek(2)] is unconstrained, and the resulting
- file offset is undefined.
-
- cmd may have the following values.
-
- ELF_C_NULL When a program sets cmd to this value, elf_begin returns
- a null pointer, without opening a new descriptor. ref is
- ignored for this command. See elf_next(3E) and the
- examples below for more information.
-
- ELF_C_READ When a program wishes to examine the contents of an
- existing file, it should set cmd to this value.
- Depending on the value of ref, this command examines
- archive members or entire files. Three cases can occur.
-
- First, if ref is a null pointer, elf_begin allocates a
- new ELF descriptor and prepares to process the entire
- file. If the file being read is an archive, elf_begin
- also prepares the resulting descriptor to examine the
- initial archive member on the next call to elf_begin, as
- if the program had used elf_next or elf_rand to ``move''
- to the initial member.
-
- Second, if ref is a non-null descriptor associated with
- an archive file, elf_begin lets a program obtain a
- separate ELF descriptor associated with an individual
- member. The program should have used elf_next or
- elf_rand to position ref appropriately (except for the
- initial member, which elf_begin prepares; see the example
- below). In this case, fildes should be the same file
- descriptor used for the parent archive.
-
- Finally, if ref is a non-null ELF descriptor that is not
- an archive, elf_begin increments the number of
- activations for the descriptor and returns ref, without
- allocating a new descriptor and without changing the
- descriptor's read/write permissions. To terminate the
-
- Page 1 Release 6.2
-
- elf_begin(3E) Silicon Graphics elf_begin(3E)
-
- descriptor for ref, the program must call elf_end once
- for each activation. See elf_next(3E) and the examples
- below for more information.
-
- ELF_C_READ_MMAP This command duplicates the actions of ELF_C_READ but
- uses the mmap() system call to access the file data in a
- more memory efficient manner. If, after libelf has
- opened the file, another process truncates the file
- libelf could get a Segmentation Violation attempting to
- read data it believes is in the file (but which is no
- longer there due to the truncation). Applications
- calling libelf with ELF_C_READ_MMAP may therefore wish to
- install a signal handler for SIGSEGV (Segmentation
- Violation) and issue a message when it happens.
-
- ELF_C_RDWR This command duplicates the actions of ELF_C_READ and
- additionally allows the program to update the file image
- [see elf_update(3E)]. That is, using ELF_C_READ gives a
- read-only view of the file, while ELF_C_RDWR lets the
- program read and write the file. ELF_C_RDWR is not valid
- for archive members. If ref is non-null, it must have
- been created with the ELF_C_RDWR command.
-
- ELF_C_WRITE If the program wishes to ignore previous file contents,
- presumably to create a new file, it should set cmd to
- this value. ref is ignored for this command.
-
- ELF_C_WRITE_FAST
- is the same as ELF_C_WRITE except that instead of
- malloc()ing memory for the output file (and then doing a
- write(2) and free()) ELF_C_WRITE_FAST writes the output
- directly to the file system (by doing writes as needed).
- Avoiding the malloc() can help limit time-consuming
- paging activity.
-
- elf_begin ``works'' on all files (including files with zero bytes),
- providing it can allocate memory for its internal structures and read any
- necessary information from the file. Programs reading object files thus
- may call elf_kind or elf_getehdr to determine the file type (only object
- files have an ELF header). If the file is an archive with no more
- members to process, or an error occurs, elf_begin returns a null pointer.
- Otherwise, the return value is a non-null ELF descriptor.
-
- Before the first call to elf_begin, a program must call elf_version to
- coordinate versions.
-
- SYSTEM SERVICES
- When processing a file, the library decides when to read or write the
- file, depending on the program's requests. Normally, the library assumes
- the file descriptor remains usable for the life of the ELF descriptor.
- If, however, a program must process many files simultaneously and the
- underlying operating system limits the number of open files, the program
-
- Page 2 Release 6.2
-
- elf_begin(3E) Silicon Graphics elf_begin(3E)
-
- can use elf_cntl to let it reuse file descriptors. After calling
- elf_cntl with appropriate arguments, the program may close the file
- descriptor without interfering with the library.
-
- All data associated with an ELF descriptor remain allocated until elf_end
- terminates the descriptor's last activation. After the descriptors have
- been terminated, the storage is released; attempting to reference such
- data gives undefined behavior. Consequently, a program that deals with
- multiple input (or output) files must keep the ELF descriptors active
- until it finishes with them.
-
- EXAMPLES
- A prototype for reading a file appears below. If the file is a simple
- object file, the program executes the loop one time, receiving a null
- descriptor in the second iteration. In this case, both elf and arf will
- have the same value, the activation count will be two, and the program
- calls elf_end twice to terminate the descriptor. If the file is an
- archive, the loop processes each archive member in turn, ignoring those
- that are not object files.
-
- if (elf_version(EV_CURRENT) == EV_NONE)
- {
- /* library out of date */
- /* recover from error */
- }
- cmd = ELF_C_READ;
- arf = elf_begin(fildes, cmd, (Elf *)0);
- while ((elf = elf_begin(fildes, cmd, arf)) != 0)
- {
- if ((ehdr = elf32_getehdr(elf)) != 0)
- {
- /* process the file ... */
- }
- cmd = elf_next(elf);
- elf_end(elf);
- }
- elf_end(arf);
-
- Alternatively, the next example illustrates random archive processing.
- After identifying the file as an archive, the program repeatedly
- processes archive members of interest. For clarity, this example omits
- error checking and ignores simple object files. Additionally, this
- fragment preserves the ELF descriptors for all archive members, because
- it does not call elf_end to terminate them.
-
- Page 3 Release 6.2
-
- elf_begin(3E) Silicon Graphics elf_begin(3E)
-
- elf_version(EV_CURRENT);
- arf = elf_begin(fildes, ELF_C_READ, (Elf *)0);
- if (elf_kind(arf) != ELF_K_AR)
- {
- /* not an archive */
- }
- /* initial processing */
- /* set offset = ... for desired member header */
- while (elf_rand(arf, offset) == offset)
- {
- if ((elf = elf_begin(fildes, ELF_C_READ, arf)) == 0)
- break;
- if ((ehdr = elf32_getehdr(elf)) != 0)
- {
- /* process archive member ... */
- }
- /* set offset = ... for desired member header */
- }
-
- The following outline shows how one might create a new ELF file. This
- example is simplified to show the overall flow.
-
- elf_version(EV_CURRENT);
- fildes = open("path/name", O_RDWR|O_TRUNC|O_CREAT, 0666);
- if ((elf = elf_begin(fildes, ELF_C_WRITE, (Elf *)0)) == 0)
- return;
- ehdr = elf32_newehdr(elf);
- phdr = elf32_newphdr(elf, count);
- scn = elf_newscn(elf);
- shdr = elf32_getshdr(scn);
- data = elf_newdata(scn);
- elf_update(elf, ELF_C_WRITE);
- elf_end(elf);
-
- Finally, the following outline shows how one might update an existing ELF
- file. Again, this example is simplified to show the overall flow.
-
- elf_version(EV_CURRENT);
- fildes = open("path/name", O_RDWR);
- elf = elf_begin(fildes, ELF_C_RDWR, (Elf *)0);
-
- /* add new or delete old information ... */
-
- close(creat("path/name", 0666));
- elf_update(elf, ELF_C_WRITE);
- elf_end(elf);
-
- In the example above, the call to creat truncates the file, thus ensuring
- the resulting file will have the ``right'' size. Without truncation, the
- updated file might be as big as the original, even if information were
- deleted. The library truncates the file, if it can, with ftruncate [see
- truncate(2)]. Some systems, however, do not support ftruncate, and the
-
- Page 4 Release 6.2
-
- elf_begin(3E) Silicon Graphics elf_begin(3E)
-
- call to creat protects against this.
-
- Notice that both file creation examples open the file with write and read
- permissions. The library is not compiled to use mmap so there is no need
- for write permission. But for maximum portability with implementations
- that do use mmap for file creation you may wish to provide both write and
- read permissions.
-
- SEE ALSO
- creat(2), lseek(2), mmap(2), open(2), truncate(2), elf(3E), elf_cntl(3E),
- elf_end(3E), elf_getarhdr(3E), elf_getbase(3E), elf_getdata(3E),
- elf_getehdr(3E), elf_getphdr(3E), elf_getscn(3E), elf_kind(3E),
- elf_next(3E), elf_rand(3E), elf_rawfile(3E), elf_update(3E),
- elf_version(3E), ar(4).
-
- NOTES
- COFF is an object file format that preceded ELF . COFF object files
- cannot be used with this library.
-
- ELF_C_READ_MMAP and ELF_C_WRITE_FAST are options specific to this
- implementation, not options which are generally available.
-
- Page 5 Release 6.2
-